home *** CD-ROM | disk | FTP | other *** search
- /*
- ** patch.library
- **
- ** Copyright © 1993-1997 by Stefan Fuchs
- ** Freely distributable.
- */
-
- #ifndef _PATCH_INCLUDES_H
- #include "patch_includes.h"
- #endif
-
- #define INSTR_JMP 0x4ef9
- #define INSTR_JSR 0x4eb9
-
-
- /****i* patch.library/ReturnD1 ***************************************
- *
- * NAME
- * ReturnD1 -- Set register d1 to a specific value.
- *
- * SYNOPSIS
- * ReturnD1( value )
- *
- * ReturnD1( ULONG );
- *
- * FUNCTION
- * Set register d1 to a specific value.
- *
- * INPUTS
- * value = value to be placed in register d1.
- *
- * NOTES
- * Hopefully this function is not removed by the compiler.
- *
- ******************************************************************************
- *
- */
- void ASMFUNC ReturnD1( REGD1 ULONG result GNUC_REGD1)
- {
- }
-
-
- /****i* patch.library/GetNumberOfNodes ***************************************
- *
- * NAME
- * GetNumberOfNodes -- Return the number of nodes in a List.
- *
- * SYNOPSIS
- * Number = GetNumberOfNodes( list )
- *
- * ULONG GetNumberOfNodes( struct List *);
- *
- * FUNCTION
- * Return the number of nodes in an exec list.
- *
- * INPUTS
- * list = pointer to a List structure
- *
- * RESULT
- * Number = Number of nodes in the given exec list.
- *
- * BUGS
- *
- ******************************************************************************
- *
- */
-
- LONG GetNumberOfNodes(struct List *header)
- {
- LONG counter = - 2;
-
- do
- {
- counter++;
- header = (struct List *)header->lh_Head;
- }
- while(header);
- return(counter);
- }
-
-
- /****i* patch.library/ADeleteMyListNode ***************************************
- *
- * NAME
- * ADeleteMyListNode -- Remove and deallocate node.
- *
- * SYNOPSIS
- * ADeleteMyListNode( node )
- *
- * ADeleteMyListNode( struct Node *);
- *
- * FUNCTION
- * Remove and deallocate exec node. This node must have been created by one
- * of the ACreateMyListNode* () functions.
- *
- * INPUTS
- * node = pointer to a node structure or NULL for no action
- *
- * RESULT
- *
- * NOTES
- *
- * BUGS
- *
- * SEE ALSO
- * ACreateMyListNode(), AFreemem()
- *
- ******************************************************************************
- *
- */
-
-
- void ADeleteMyListNode( struct Node *node)
- {
- if(node)
- {
- Remove(node);
- AFreemem(node);
- }
- }
-
-
- /****i* patch.library/ACreateMyListNodeNamed ***************************************
- *
- * NAME
- * ACreateMyListNodeNamed -- Create and add a named node.
- *
- * SYNOPSIS
- * node = ACreateMyListNodeNamed( list, length, name )
- *
- * struct Node *ACreateMyListNodeNamed( struct List *, ULONG, STRPTR );
- *
- * FUNCTION
- * Create a node structure of the given size and name and add it to
- * the given list.
- * This node can be removed by a call to ADeleteMyListNode().
- *
- * INPUTS
- * list = pointer to a list structure
- * length = size of node in bytes
- * name = name of the node to add or NULL, for an unnamed node
- *
- * RESULT
- * node = pointer to the newly created node structure or NULL on failure
- *
- * NOTES
- *
- * BUGS
- *
- * SEE ALSO
- * ACreateMyListNode(), ADeleteMyListNode(), BAllocmem()
- *
- ******************************************************************************
- *
- */
-
- struct Node *ACreateMyListNodeNamed(struct List *header, ULONG length, STRPTR string)
- {
- struct Node *pointer;
- if(string)
- {
- pointer = (struct Node *)BAllocmem( length + strlen( string) + 1, MEMF_CLEAR | MEMF_PUBLIC);
- if(pointer)
- {
- pointer->ln_Name = strcpy((char *) ((ULONG)pointer+length), string);
- AddTail( header, pointer);
- }
- }
- else
- {
- pointer = ACreateMyListNode( header, length);
- }
- return(pointer);
- }
-
-
- /****i* patch.library/ACreateMyListNode ***************************************
- *
- * NAME
- * ACreateMyListNode -- Create and add a node.
- *
- * SYNOPSIS
- * node = ACreateMyListNode( list, length )
- *
- * struct Node *ACreateMyListNode( struct List *, ULONG);
- *
- * FUNCTION
- * Create a node structure of the given size and add it to
- * the given list.
- * This node can be removed by a call to ADeleteMyListNode().
- *
- * INPUTS
- * list = pointer to a list structure or NULL for no action
- * length = size of node in bytes
- *
- * RESULT
- * node = pointer to the newly created node structure or NULL on failure
- *
- * NOTES
- *
- * BUGS
- *
- * SEE ALSO
- * ACreateMyListNode(), ADeleteMyListNode(), BAllocmem()
- *
- ******************************************************************************
- *
- */
-
- struct Node *ACreateMyListNode(struct List *header, ULONG length)
- {
- struct Node *pointer = 0;
- if(header)
- {
- pointer = (struct Node *)BAllocmem( length, MEMF_CLEAR | MEMF_PUBLIC);
- if(pointer) AddTail( header, pointer);
- }
- return(pointer);
- }
-
-
- /****i* patch.library/ACreateMyListNodeNamedPri ***************************************
- *
- * NAME
- * ACreateMyListNodeNamedPri -- Create and add a named node with priority.
- *
- * SYNOPSIS
- * node = ACreateMyListNodeNamedPri( list, length, name, priority )
- *
- * struct Node *ACreateMyListNodeNamedPri( struct List *, ULONG, STRPTR, BYTE );
- *
- * FUNCTION
- * Create a node structure of the given size and name and add it to
- * the given list with the given priority.
- * This node can be removed by a call to ADeleteMyListNode().
- *
- * INPUTS
- * list = pointer to a list structure
- * length = size of node in bytes
- * name = name of the node to add or NULL, for an unnamed node
- * priority = position at which the node is to be added to the list
- *
- * RESULT
- * node = pointer to the newly created node structure or NULL on failure
- *
- * NOTES
- *
- * BUGS
- *
- * SEE ALSO
- * ACreateMyListNode(), ADeleteMyListNode(), BAllocmem(), EnqueueLIFO()
- *
- ******************************************************************************
- *
- */
-
- struct Node *ACreateMyListNodeNamedPri(struct List *header, ULONG length, STRPTR string, BYTE pri)
- {
- struct Node *pointer;
- if(string)
- {
- pointer = (struct Node *)BAllocmem( length + strlen( string) + 1, MEMF_CLEAR | MEMF_PUBLIC);
- if(pointer)
- {
- pointer->ln_Name = strcpy((char *) ((ULONG)pointer+length), string);
- pointer->ln_Pri = pri;
- EnqueueLIFO( header, pointer);
- }
- }
- else
- {
- pointer = ACreateMyListNodePri( header, length, pri);
- }
- return(pointer);
- }
-
-
- /****i* patch.library/ACreateMyListNodePri ***************************************
- *
- * NAME
- * ACreateMyListNodePri -- Create and add a node with priority.
- *
- * SYNOPSIS
- * node = ACreateMyListNodePri( list, length, priority )
- *
- * struct Node *ACreateMyListNodePri( struct List *, ULONG, BYTE );
- *
- * FUNCTION
- * Create a node structure of the given size and add it to
- * the given list with the given priority.
- * This node can be removed by a call to ADeleteMyListNode().
- *
- * INPUTS
- * list = pointer to a list structure or NULL for no action
- * length = size of node in bytes
- * priority = position at which the node is to be added to the list
- *
- * RESULT
- * node = pointer to the newly created node structure or NULL on failure
- *
- * NOTES
- *
- * BUGS
- *
- * SEE ALSO
- * ACreateMyListNode(), ADeleteMyListNode(), BAllocmem(), EnqueueLIFO()
- *
- ******************************************************************************
- *
- */
-
- struct Node *ACreateMyListNodePri(struct List *header, ULONG length, BYTE pri)
- {
- struct Node *pointer = 0;
- if(header)
- {
- pointer = (struct Node *)BAllocmem( length, MEMF_CLEAR | MEMF_PUBLIC);
- if(pointer)
- {
- pointer->ln_Pri = pri;
- EnqueueLIFO( header, pointer);
- }
- }
- return(pointer);
- }
-
-
- /****i* patch.library/AAllocmem ***************************************
- *
- * NAME
- * AAllocmem -- Allocate memory from the memory pool remembering
- * its size.
- *
- * SYNOPSIS
- * memory = AAllocmem( size, attributes, pool )
- *
- * APTR AAllocmem( ULONG, ULONG, APTR );
- *
- * FUNCTION
- * Allocate memory from the global or (if it exists) from a local
- * memory pool and remember its size.
- * Deallocate this memory with AFreemem().
- *
- * INPUTS
- * size = number of bytes to allocate
- * attributes = memory attributes (only required, if pool is NULL)
- * pool = pointer to a memorypool as returned by CreatePool() or NULL, if
- * memory should be allocated from the global memory.
- *
- * RESULT
- * memory = pointer to newly allocated memory block or NULL on failure
- *
- * NOTES
- *
- * BUGS
- *
- * SEE ALSO
- * Allocmem(), AllocVec(), AFreemem(), CreatePool()
- *
- ******************************************************************************
- *
- */
-
-
- APTR AAllocmem( ULONG size, ULONG attr, APTR pool)
- {
- ULONG *memory;
-
- size += 8;
- if( pool)
- {
- memory = LibAllocPooled( pool, size);
- }
- else
- {
- memory = AllocMem( size, attr);
- }
-
- if (memory)
- {
- *memory++ = size;
- *memory++ = (ULONG)pool;
- }
- return( memory);
- }
-
-
- /****i* patch.library/AFreemem ***************************************
- *
- * NAME
- * AFreemem -- Free memory allocated from the memory pool.
- *
- * SYNOPSIS
- * AFreemem( memory )
- *
- * AFreemem( APTR );
- *
- * FUNCTION
- * Free memory from the global or from a local
- * memory pool.
- * This memory must have been allocated with AAllocmem().
- *
- * INPUTS
- * memory = pointer to memoryblock
- *
- * RESULT
- *
- * NOTES
- *
- * BUGS
- *
- * SEE ALSO
- * AAllocmem()
- *
- ******************************************************************************
- *
- */
-
- void AFreemem( APTR memory)
- {
- ULONG *mem;
- if( memory)
- {
- mem = (ULONG *)memory - 2;
- if (mem[1])
- LibFreePooled((APTR) mem[1], mem, mem[0]);
- else
- FreeMem( mem, mem[0]);
- }
- }
-
-
- /****i* patch.library/MyDelay ***************************************
- *
- * NAME
- * MyDelay -- Delay a task for a number of ticks.
- *
- * SYNOPSIS
- * MyDelay( ticks )
- *
- * MyDelay( ULONG );
- *
- * FUNCTION
- * Put a task a number of ticks (1/50 seconds) to sleep.
- *
- * INPUTS
- * ticks = number of ticks (1/50 seconds) to wait
- *
- * RESULT
- *
- * NOTES
- * This function has been written as it is unclear wether
- * dos.library/Delay() may be called from tasks or not.
- *
- * BUGS
- * Number of ticks is restricted to about a minute
- *
- * SEE ALSO
- * dos.library/Delay()
- *
- ******************************************************************************
- *
- */
-
- void MyDelay( LONG time)
- {
- struct MsgPort *msgport;
- struct IORequest *iorequest;
-
- if( msgport = CreateMsgPort())
- {
- if( iorequest = CreateExtIO( msgport, sizeof(struct timerequest)))
- {
- if( !OpenDevice("timer.device", UNIT_VBLANK, iorequest, 0L))
- {
- ((struct timerequest *)iorequest)->tr_time.tv_secs = 0;
- ((struct timerequest *)iorequest)->tr_time.tv_micro = time * 20000;
- ((struct timerequest *)iorequest)->tr_node.io_Command = TR_ADDREQUEST;
-
- DoIO( iorequest);
-
- CloseDevice( iorequest);
- }
- DeleteExtIO( iorequest);
- }
- DeleteMsgPort(msgport);
- }
- }
-
- /****i* patch.library/FindNameNoCase ***************************************
- *
- * NAME
- * FindNameNoCase -- Search an exec-list not case-sensitive.
- *
- * SYNOPSIS
- * node = FindNameNoCase( list, string )
- *
- * struct Node *FindNameNoCase( struct List *, STRPTR );
- *
- * FUNCTION
- * Search an exec-list not case-sensitive.
- *
- * INPUTS
- * list = pointer to List structure to search or NULL for no action
- * string = C-String or NULL for no action.
- *
- * RESULT
- * node = pointer to node structure or NULL, if not found
- *
- * NOTES
- *
- * BUGS
- *
- * SEE ALSO
- * exec.library/FindName()
- *
- ******************************************************************************
- *
- */
-
- struct Node *FindNameNoCase( struct List *header, STRPTR name)
- {
- struct Node *pointer = NULL;
-
- if( (header) && (name))
- {
- for( pointer = header->lh_Head;
- pointer->ln_Succ;
- pointer = pointer->ln_Succ)
- {
- if (stricmp( pointer->ln_Name, name) == 0L)
- break;
- }
- }
- return( pointer);
- }
-
-
- /****i* patch.library/FindType ***************************************
- *
- * NAME
- * FindType -- Search an exec-list for a node of the given type.
- *
- * SYNOPSIS
- * node = FindType( list, type )
- *
- * struct Node *FindType( struct List *, UBYTE );
- *
- * FUNCTION
- * Search an exec-list fo a node of the given type.
- *
- * INPUTS
- * list = pointer to List structure to search
- * type = Type of node to search for.
- *
- * RESULT
- * node = pointer to node structure or NULL, if not found
- *
- * NOTES
- *
- * BUGS
- *
- * SEE ALSO
- *
- ******************************************************************************
- *
- */
-
-
- struct Node *FindType( struct List *header, UBYTE type)
- {
- struct Node *pointer;
- for (pointer = (struct Node *)header->lh_Head;
- pointer->ln_Succ;
- pointer = (struct Node *)pointer->ln_Succ)
- {
- if( pointer->ln_Type == type) return( pointer);
- }
- return( NULL);
- }
-
-
- /****i* patch.library/GetListNodeHeader ***************************************
- *
- * NAME
- * GetListNodeHeader -- Get a List structure to a given node.
- *
- * SYNOPSIS
- * list = GetListNodeHeader( node )
- *
- * struct List *FindType( struct Node * );
- *
- * FUNCTION
- * Get a pointer to the List structure of a given node.
- *
- * INPUTS
- * node = pointer to a Node structure
- *
- * RESULT
- * list = pointer to List structure
- *
- * NOTES
- * The node MUST belong to a List or everything might happen.
- *
- * BUGS
- *
- * SEE ALSO
- *
- ******************************************************************************
- *
- */
-
- struct List *GetListNodeHeader( struct Node *pointer)
- {
- for(;(pointer->ln_Succ);pointer = pointer->ln_Succ);
- pointer = (struct Node *)(((ULONG *)pointer) - 1);
- return( (struct List *)pointer);
- }
-
-
- /****i* patch.library/EnqueueLIFO ***************************************
- *
- * NAME
- * EnqueueLIFO -- Insert nodes in front of the first node
- * with the same priority
- *
- * SYNOPSIS
- * EnqueueLIFO( list, node )
- *
- * EnqueueLIFO( struct List *, struct Node * );
- *
- * FUNCTION
- * Insert a node in front of the first node with the same priority
- * (Last in, First out - style)
- *
- * INPUTS
- * list = pointer to List structure or NULL for no action
- * node = pointer to Node structure or NULL for no action
- *
- * RESULT
- *
- * NOTES
- * exec.library/Enqueue() works in FIFO - style.
- *
- * BUGS
- *
- * SEE ALSO
- * exec.library/Enqueue()
- *
- ******************************************************************************
- *
- */
-
-
- void EnqueueLIFO( struct List *header, struct Node *newnode)
- {
- struct Node *pointer;
- if( (header) && (newnode))
- {
- for (pointer = (struct Node *)header->lh_Head;
- pointer->ln_Succ;
- pointer = (struct Node *)pointer->ln_Succ)
- {
- if( pointer->ln_Succ->ln_Succ == NULL) break;
- if( newnode->ln_Pri >= pointer->ln_Succ->ln_Pri) break;
- }
- if( header == (struct List *)pointer)
- {
- AddHead( header, newnode);
- }
- else
- {
- Insert( header, newnode, pointer);
- }
- }
- }
-
- /****i* patch.library/SetJMPInstr ***************************************
- *
- * NAME
- * SetJMPInstr -- Modify a jump instruction
- *
- * SYNOPSIS
- * SetJMPInstr( memory, destination )
- *
- * SetJMPInstr( UBYTE *, APTR );
- *
- * FUNCTION
- * Modify a (68K) jump instruction at a given location in memory to
- * point to a new adress (destination).
- *
- * INPUTS
- * memory = memory location, where to place the instruction or
- * NULL for no action
- * destination = memory location, to which the jump instruction is set
- *
- * RESULT
- *
- * NOTES
- * On processors with cache this function must be enclosed by
- * disable(), FlushCache(), Enable().
- * This function has been introduced to make patch.library
- * portable.
- *
- * BUGS
- *
- * SEE ALSO
- *
- ******************************************************************************
- *
- */
-
-
- void SetJMPInstr( UBYTE *memptr, APTR destination)
- {
- if( memptr)
- {
- *((UWORD *)memptr) = INSTR_JMP;
- memptr += 2;
- *((ULONG *)memptr) = (ULONG)destination;
- }
- }
- /****i* patch.library/SetJSRInstr ***************************************
- *
- * NAME
- * SetJSRInstr -- Modify a jump-subroutine instruction
- *
- * SYNOPSIS
- * SetJSRInstr( memory, destination )
- *
- * SetJSRInstr( UBYTE *, APTR );
- *
- * FUNCTION
- * Modify a (68K) jump-subroutine instruction at a given location
- * in memory to point to a new adress (destination).
- *
- * INPUTS
- * memory = memory location, where to place the instruction or
- * NULL for no action
- * destination = memory location, to which the jsr instruction is set
- *
- * RESULT
- *
- * NOTES
- * On processors with cache this function must be enclosed by
- * disable(), FlushCache(), Enable().
- * This function has been introduced to make patch.library
- * portable.
- *
- * BUGS
- *
- * SEE ALSO
- *
- ******************************************************************************
- *
- */
-
-
- void SetJSRInstr( UBYTE *memptr, APTR destination)
- {
- if( memptr)
- {
- *((UWORD *)memptr) = INSTR_JSR;
- memptr += 2;
- *((ULONG *)memptr) = (ULONG)destination;
- }
- }
-